package com.automannn.practice.mybatis.parameterHandler;

import com.automannn.practice.mybatis.paramResolver.ParamNameResolverTest;
import org.apache.ibatis.builder.StaticSqlSource;
import org.apache.ibatis.executor.parameter.ParameterHandler;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.mapping.ParameterMapping;
import org.apache.ibatis.mapping.SqlCommandType;
import org.apache.ibatis.mapping.SqlSource;
import org.apache.ibatis.scripting.defaults.DefaultParameterHandler;
import org.apache.ibatis.session.Configuration;
import org.apache.ibatis.type.StringTypeHandler;

import java.io.InputStream;
import java.io.Reader;
import java.math.BigDecimal;
import java.net.URL;
import java.sql.*;
import java.sql.Blob;
import java.sql.Clob;
import java.sql.NClob;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;

/**
 * @author chenkh
 * @time 2021/10/26 15:05
 */
public class ParameterHandlerTest {
    public static void main(String[] args) throws SQLException {
        Configuration configuration = new Configuration();
        List<ParameterMapping> parameterMappings = new ArrayList<>();
        ParameterMapping parameterMapping = new ParameterMapping.Builder(configuration,"pname", QueryEntity.class).typeHandler(new StringTypeHandler()).build();
        parameterMappings.add(parameterMapping);
        SqlSource sqlSource = new StaticSqlSource(configuration,"select * from person",parameterMappings);
        MappedStatement mappedStatement = new MappedStatement.Builder(configuration,"myMethod",sqlSource, SqlCommandType.SELECT).build();


        QueryEntity entity = new QueryEntity();
        entity.setLength(10);
        entity.setPid("L001");
        entity.setPname("test");
        entity.setSize("big");

        /*xxx: 获取参数属性时，如果是对象，可以直接根据属性获取参数 */
        /*xxx: 单个参数，且为 基本数据类型，时间类型等，任意ognl表达式都可以获取*/
        /*xxx: 单个参数，且为 对象类型时，  可以通过 反射获取参数  */
        /*xxx: 多个参数， 则要根据 paramResolver的规则来 */
        ParameterHandler parameterHandler = new DefaultParameterHandler(mappedStatement,entity,sqlSource.getBoundSql(entity));
        PreparedStatement preparedStatement = new PreparedStatement() {
            @Override
            public ResultSet executeQuery() throws SQLException {
                return null;
            }

            @Override
            public int executeUpdate() throws SQLException {
                return 0;
            }

            @Override
            public void setNull(int parameterIndex, int sqlType) throws SQLException {

            }

            @Override
            public void setBoolean(int parameterIndex, boolean x) throws SQLException {

            }

            @Override
            public void setByte(int parameterIndex, byte x) throws SQLException {

            }

            @Override
            public void setShort(int parameterIndex, short x) throws SQLException {

            }

            @Override
            public void setInt(int parameterIndex, int x) throws SQLException {

            }

            @Override
            public void setLong(int parameterIndex, long x) throws SQLException {

            }

            @Override
            public void setFloat(int parameterIndex, float x) throws SQLException {

            }

            @Override
            public void setDouble(int parameterIndex, double x) throws SQLException {

            }

            @Override
            public void setBigDecimal(int parameterIndex, BigDecimal x) throws SQLException {

            }

            @Override
            public void setString(int parameterIndex, String x) throws SQLException {

            }

            @Override
            public void setBytes(int parameterIndex, byte[] x) throws SQLException {

            }

            @Override
            public void setDate(int parameterIndex, Date x) throws SQLException {

            }

            @Override
            public void setTime(int parameterIndex, Time x) throws SQLException {

            }

            @Override
            public void setTimestamp(int parameterIndex, Timestamp x) throws SQLException {

            }

            @Override
            public void setAsciiStream(int parameterIndex, InputStream x, int length) throws SQLException {

            }

            @Override
            public void setUnicodeStream(int parameterIndex, InputStream x, int length) throws SQLException {

            }

            @Override
            public void setBinaryStream(int parameterIndex, InputStream x, int length) throws SQLException {

            }

            @Override
            public void clearParameters() throws SQLException {

            }

            @Override
            public void setObject(int parameterIndex, Object x, int targetSqlType) throws SQLException {

            }

            @Override
            public void setObject(int parameterIndex, Object x) throws SQLException {

            }

            @Override
            public boolean execute() throws SQLException {
                return false;
            }

            @Override
            public void addBatch() throws SQLException {

            }

            @Override
            public void setCharacterStream(int parameterIndex, Reader reader, int length) throws SQLException {

            }

            @Override
            public void setRef(int parameterIndex, Ref x) throws SQLException {

            }

            @Override
            public void setBlob(int parameterIndex, Blob x) throws SQLException {

            }

            @Override
            public void setClob(int parameterIndex, Clob x) throws SQLException {

            }

            @Override
            public void setArray(int parameterIndex, Array x) throws SQLException {

            }

            @Override
            public ResultSetMetaData getMetaData() throws SQLException {
                return null;
            }

            @Override
            public void setDate(int parameterIndex, Date x, Calendar cal) throws SQLException {

            }

            @Override
            public void setTime(int parameterIndex, Time x, Calendar cal) throws SQLException {

            }

            @Override
            public void setTimestamp(int parameterIndex, Timestamp x, Calendar cal) throws SQLException {

            }

            @Override
            public void setNull(int parameterIndex, int sqlType, String typeName) throws SQLException {

            }

            @Override
            public void setURL(int parameterIndex, URL x) throws SQLException {

            }

            @Override
            public ParameterMetaData getParameterMetaData() throws SQLException {
                return null;
            }

            @Override
            public void setRowId(int parameterIndex, RowId x) throws SQLException {

            }

            @Override
            public void setNString(int parameterIndex, String value) throws SQLException {

            }

            @Override
            public void setNCharacterStream(int parameterIndex, Reader value, long length) throws SQLException {

            }

            @Override
            public void setNClob(int parameterIndex, NClob value) throws SQLException {

            }

            @Override
            public void setClob(int parameterIndex, Reader reader, long length) throws SQLException {

            }

            @Override
            public void setBlob(int parameterIndex, InputStream inputStream, long length) throws SQLException {

            }

            @Override
            public void setNClob(int parameterIndex, Reader reader, long length) throws SQLException {

            }

            @Override
            public void setSQLXML(int parameterIndex, SQLXML xmlObject) throws SQLException {

            }

            @Override
            public void setObject(int parameterIndex, Object x, int targetSqlType, int scaleOrLength) throws SQLException {

            }

            @Override
            public void setAsciiStream(int parameterIndex, InputStream x, long length) throws SQLException {

            }

            @Override
            public void setBinaryStream(int parameterIndex, InputStream x, long length) throws SQLException {

            }

            @Override
            public void setCharacterStream(int parameterIndex, Reader reader, long length) throws SQLException {

            }

            @Override
            public void setAsciiStream(int parameterIndex, InputStream x) throws SQLException {

            }

            @Override
            public void setBinaryStream(int parameterIndex, InputStream x) throws SQLException {

            }

            @Override
            public void setCharacterStream(int parameterIndex, Reader reader) throws SQLException {

            }

            @Override
            public void setNCharacterStream(int parameterIndex, Reader value) throws SQLException {

            }

            @Override
            public void setClob(int parameterIndex, Reader reader) throws SQLException {

            }

            @Override
            public void setBlob(int parameterIndex, InputStream inputStream) throws SQLException {

            }

            @Override
            public void setNClob(int parameterIndex, Reader reader) throws SQLException {

            }

            @Override
            public ResultSet executeQuery(String sql) throws SQLException {
                return null;
            }

            @Override
            public int executeUpdate(String sql) throws SQLException {
                return 0;
            }

            @Override
            public void close() throws SQLException {

            }

            @Override
            public int getMaxFieldSize() throws SQLException {
                return 0;
            }

            @Override
            public void setMaxFieldSize(int max) throws SQLException {

            }

            @Override
            public int getMaxRows() throws SQLException {
                return 0;
            }

            @Override
            public void setMaxRows(int max) throws SQLException {

            }

            @Override
            public void setEscapeProcessing(boolean enable) throws SQLException {

            }

            @Override
            public int getQueryTimeout() throws SQLException {
                return 0;
            }

            @Override
            public void setQueryTimeout(int seconds) throws SQLException {

            }

            @Override
            public void cancel() throws SQLException {

            }

            @Override
            public SQLWarning getWarnings() throws SQLException {
                return null;
            }

            @Override
            public void clearWarnings() throws SQLException {

            }

            @Override
            public void setCursorName(String name) throws SQLException {

            }

            @Override
            public boolean execute(String sql) throws SQLException {
                return false;
            }

            @Override
            public ResultSet getResultSet() throws SQLException {
                return null;
            }

            @Override
            public int getUpdateCount() throws SQLException {
                return 0;
            }

            @Override
            public boolean getMoreResults() throws SQLException {
                return false;
            }

            @Override
            public void setFetchDirection(int direction) throws SQLException {

            }

            @Override
            public int getFetchDirection() throws SQLException {
                return 0;
            }

            @Override
            public void setFetchSize(int rows) throws SQLException {

            }

            @Override
            public int getFetchSize() throws SQLException {
                return 0;
            }

            @Override
            public int getResultSetConcurrency() throws SQLException {
                return 0;
            }

            @Override
            public int getResultSetType() throws SQLException {
                return 0;
            }

            @Override
            public void addBatch(String sql) throws SQLException {

            }

            @Override
            public void clearBatch() throws SQLException {

            }

            @Override
            public int[] executeBatch() throws SQLException {
                return new int[0];
            }

            @Override
            public Connection getConnection() throws SQLException {
                return null;
            }

            @Override
            public boolean getMoreResults(int current) throws SQLException {
                return false;
            }

            @Override
            public ResultSet getGeneratedKeys() throws SQLException {
                return null;
            }

            @Override
            public int executeUpdate(String sql, int autoGeneratedKeys) throws SQLException {
                return 0;
            }

            @Override
            public int executeUpdate(String sql, int[] columnIndexes) throws SQLException {
                return 0;
            }

            @Override
            public int executeUpdate(String sql, String[] columnNames) throws SQLException {
                return 0;
            }

            @Override
            public boolean execute(String sql, int autoGeneratedKeys) throws SQLException {
                return false;
            }

            @Override
            public boolean execute(String sql, int[] columnIndexes) throws SQLException {
                return false;
            }

            @Override
            public boolean execute(String sql, String[] columnNames) throws SQLException {
                return false;
            }

            @Override
            public int getResultSetHoldability() throws SQLException {
                return 0;
            }

            @Override
            public boolean isClosed() throws SQLException {
                return false;
            }

            @Override
            public void setPoolable(boolean poolable) throws SQLException {

            }

            @Override
            public boolean isPoolable() throws SQLException {
                return false;
            }

            @Override
            public void closeOnCompletion() throws SQLException {

            }

            @Override
            public boolean isCloseOnCompletion() throws SQLException {
                return false;
            }

            @Override
            public <T> T unwrap(Class<T> iface) throws SQLException {
                return null;
            }

            @Override
            public boolean isWrapperFor(Class<?> iface) throws SQLException {
                return false;
            }
        };

        parameterHandler.setParameters(preparedStatement);

    }

    public static class QueryEntity{
        private String pid;
        private String pname;
        private String size;
        private Integer length;

        public String getPid() {
            return pid;
        }

        public void setPid(String pid) {
            this.pid = pid;
        }

        public String getPname() {
            return pname;
        }

        public void setPname(String pname) {
            this.pname = pname;
        }

        public String getSize() {
            return size;
        }

        public void setSize(String size) {
            this.size = size;
        }

        public Integer getLength() {
            return length;
        }

        public void setLength(Integer length) {
            this.length = length;
        }
    }
}
